<?php

// [ 微信扫码授权回调处理 ]
// wiki
// https://open.weixin.qq.com/cgi-bin/showdocument?action=dir_list&t=resource/res_list&verify=1&id=open1419316505&token=&lang=zh_CN

namespace app\wechat\lib;
use think\Db;
use think\Config;
use think\Session;
use think\Request;
use app\common\logic\Login as LoginLogic;

class ScanOauth
{
    // 微信扫码授权登录
    // 参数说明：
    // appid          是  应用唯一标识
    // redirect_uri   是  重定向地址，需要进行UrlEncode
    // response_type  是  填code
    // scope          是  应用授权作用域，拥有多个作用域用逗号（,）分隔，网页应用目前仅填写snsapi_login即可
    // state          否  用于保持请求和回调的状态，授权请求后原样带回给第三方。该参数可用于防止csrf攻击（跨站请求伪造攻击），建议第三方带上该参数，可设置为简单的随机数加session进行校验
    // 返回说明：
    // 1.用户允许授权后，将会重定向到redirect_uri的网址上，并且带上code和state参数
    // redirect_uri?code=CODE&state=STATE
    // 2.若用户禁止授权，则重定向后不会带上code参数，仅会带上state参数
    // redirect_uri?state=STATE
    public static function uri()
    {
        $appid       = Config::get('open.appid');
        $redirectUri = urlencode(Request::instance()->domain() . '/wx_scan_oauth_callback');
        $state       = rand(100000,999999);

        // 生成授权Session验证state
        Session::set('wx_scan_oauth_state',$state);

        $uri = 'https://open.weixin.qq.com/connect/qrconnect'
             . '?appid=' . $appid
             . '&redirect_uri=' . $redirectUri
             . '&response_type=code'
             . '&scope=snsapi_login'
             . '&state=' . $state
             . '#wechat_redirect';

        return $uri;
    }

    // @param redirect_uri
    //        code
    //        state
    // @remark
    // 1.用户允许授权后，将会重定向到redirect_uri的网址上，并且带上code和state参数
    // redirect_uri?code=CODE&state=STATE
    // 2.若用户禁止授权，则重定向后不会带上code参数，仅会带上state参数
    // redirect_uri?state=STATE
    // @return success         登录成功,跳转会员中心
    //         csrf            跨站请求伪造攻击,跳转对应提示页面
    //         user_not_allow  用户禁止授权,跳转对应提示页面
    //         bind            帐号不存在,绑定用户,跳转绑定手机号页面
    public static function callback($state, $code = null)
    {
        // 验证state，防止csrf攻击（跨站请求伪造攻击）
        // if ( Session::get('wx_scan_oauth_state') != $state ) return 'csrf';

        // 清除授权Session验证state
        Session::delete('wx_scan_oauth_state');

        // 用户禁止授权
        if ( empty($code) ) return 'user_not_allow';

        $result = self::getAccessToken($code);
        // p($result);die;

        $member = Db::name('member')->where('unionid',$result['unionid'])->find();

        if ( !is_null($member) ) {
            # 帐号存在
            $member['info'] = Db::name('member_info')->where('member_id',$member['id'])->find();

            // 登录处理
            LoginLogic::run($member);

            return 'success';
        } else {
            # 帐号不存在
            $userinfo = self::getUserInfo($result['access_token'],$result['openid']);
            // p($userinfo);

            // 写入Session
            Session::set('wechat',$userinfo);

            return 'bind';
        }
    }

    // 第二步：通过code获取access_token
    /*
    Array
    (
        [access_token]  => RB2ZkgXh5ZJfv21H1lqV0FIfqp6asVPjVDvQFw-5XtA_y8UrOQWZ14i17hZsIeWA-29GMc_86TSCMCYekViD8Heq9s399CJ23Wfk5c8ybjs
        [expires_in]    => 7200
        [refresh_token] => D1Rwc03shZHnKM-NUaRt-qEpm3H9gJK1nfZHy7iwpP4w24ZuMz6y18YHbzkH_bYK4-s8jDFceQ6CrKTjOmGQeC5168zNbF3wWwvz8MFeuO8
        [openid]        => o0XAB02xF8Hp_UE3-XOgZa-i3Q78
        [scope]         => snsapi_login
        [unionid]       => okpjT0qwLBr1L41ZLesDFUqhJcf4
    )
    */
    public static function getAccessToken($code)
    {
        $appid     = Config::get('open.appid');
        $appsecret = Config::get('open.appsecret');
        $uri = 'https://api.weixin.qq.com/sns/oauth2/access_token'
             . '?appid=' . $appid
             . '&secret=' . $appsecret
             . '&code=' . $code
             . '&grant_type=authorization_code';
        $res = https_curl($uri);
        $res = json_decode($res,true);
        return $res;
    }

    // 第三步：通过access_token和openid获取用户信息
    /*
    Array
    (
        "openid"     => "o0XAB02xF8Hp_UE3-XOgZa-i3Q78",
        "nickname"   => "明日东华｜曾凡东",
        "sex"        => 1,
        "language"   => "zh_CN",
        "city"       => "Chengdu",
        "province"   => "Sichuan",
        "country"    => "CN",
        "headimgurl" => "http=>//wx.qlogo.cn/mmopen/lX23BY3j9bdiamGdO3eAjrbKHicroobVU4VVshs98crrzp2tOrBd7sxqqiaiaADENJTrDIpKQk8JqyY3Znhp6u08YbQ0UewxZvjF/0",
        "privilege"  => [],
        "unionid"    => "okpjT0qwLBr1L41ZLesDFUqhJcf4"
    )
    */
    public static function getUserInfo($accessToken, $openid)
    {
        $uri = 'https://api.weixin.qq.com/sns/userinfo'
             . '?access_token=' . $accessToken
             . '&openid=' . $openid;
        $res = https_curl($uri);
        $res = json_decode($res,true);
        return $res;
    }
}
